"""
=============================================================================
SCRIPT: AnthrOS_Infrastructure_Compiler.py
CODENAME: "The Tank"
PROJECT: Project AnthroHeart
AUTHOR: Thomas B. Sweet aka Anthro Teacher/Cio
UPDATES:
- Converted to Perplexity API
- Added Windows Long Path support (\\\\?\\ prefix).
- Added Error Skipping (Script won't crash on one bad file).
- Forces Absolute Paths to prevent "Path not found" errors.
=============================================================================
"""

import os
import shutil
import json
import random
import time
import textwrap
import logging
from pathlib import Path
from datetime import datetime

# ==========================================
# 1. CORE LIBRARIES
# ==========================================
print("\n[ SYSTEM ] Booting AnthrOS Infrastructure (Robust Mode)...")
try:
    from openai import OpenAI
    from PIL import Image, ImageDraw, ImageFont
    from fpdf import FPDF
    import requests
    import mutagen
    from mutagen.id3 import ID3, TIT2, TPE1, TALB, TCON, COMM, APIC, TXXX
    from mutagen.wave import WAVE
    from pypdf import PdfReader, PdfWriter
except ImportError as e:
    print(f"\n[ CRITICAL ] Missing Library: {e}")
    print("Run: pip install openai pillow mutagen pypdf fpdf requests")
    exit()

# ==========================================
# 2. CONFIGURATION MATRIX
# ==========================================
NEXUS_URL = "https://nexus.anthroentertainment.com"
BRANDING = {
    "project_name": "Project AnthroHeart",
    "version": "AnthrOS 1.0",
    "author": "Thomas B. Sweet",
    "website": "anthroentertainment.com",
    "warlock_artist_1": "certaintlyart.anthroentertainment.com",
    "warlock_artist_2": "orbnorsolyaart.anthroentertainment.com",
}

ECOSYSTEM = {
    "WordFinder": "wordfinder.anthroentertainment.com",
    "Tarot": "tarot.anthroentertainment.com",
    "ButCanHeDraw": "butcanhedraw.anthroentertainment.com",
    "Servitor": "servitorconnect.anthroentertainment.com",
    "History": "myfirstcomputer.anthroentertainment.com",
    "MagnumOpus": "magnumopus.anthroentertainment.com"
}

ASSETS = {
    "blueheartfoxicon.png": "http://foxicon.anthroentertainment.com",
    "dogicon.png": "http://dogicon.anthroentertainment.com",
    "anthronessgemicon.png": "http://gemicon.anthroentertainment.com",
    "trinityicon.png": "http://trinityicon.anthroentertainment.com",
    "anthroheartreceipt.png": "http://receipt.anthroentertainment.com"
}

OUTPUT_DIR = "Updated_AnthroHeart_Archive"
HOLLYWOOD_DIR = "Hollywood_Pitch_Package"
CACHE_DIR = "anthros_assets_cache"
ZINGERS = [
    "Fur is temporary, style is forever.",
    "Paws off the merchandise.",
    "Barking up the right tree.",
    "404: Human not found.",
    "Digital hearts, analog souls.",
    "Welcome to the pack.",
    "The Warlock sees all."
]

# ==========================================
# 3. AUTHENTICATION (PERPLEXITY)
# ==========================================
def get_api_key():
    try:
        key_path = Path("..") / "Perplexity_Key.txt"
        with open(key_path, "r") as f: 
            return f.read().strip()
    except:
        print("[ ERROR ] API Key missing. Check '../Perplexity_Key.txt'")
        exit()

# Initialize Perplexity client with OpenAI-compatible interface
client = OpenAI(
    api_key=get_api_key(),
    base_url="https://api.perplexity.ai"
)

# ==========================================
# 4. ASSET ACQUISITION
# ==========================================
def acquire_assets():
    print(f"[ NET ] Connecting to AnthrOS Subdomains...")
    if not os.path.exists(CACHE_DIR): os.mkdir(CACHE_DIR)
    downloaded = {}
    for filename, url in ASSETS.items():
        local = Path(CACHE_DIR) / filename
        try:
            headers = {'User-Agent': 'AnthrOS-Compiler/1.0'}
            r = requests.get(url, headers=headers, timeout=15, allow_redirects=True)
            if r.status_code == 200:
                with open(local, 'wb') as f: f.write(r.content)
                downloaded[filename] = local
                print(f"  + Downloaded: {filename}")
            else:
                if local.exists(): downloaded[filename] = local
        except:
            if local.exists(): downloaded[filename] = local
    return downloaded

# ==========================================
# 5. AI INTELLIGENCE (PERPLEXITY)
# ==========================================
def analyze_file(filename):
    prompt = f"""
Analyze file: "{filename}".
Context: "The Warlock Name" (Art Copyright, Story CC0). "Project AnthroHeart" (CC0).
Return JSON: {{"is_warlock": bool, "type": "art/audio/text/pdf/other", "artist": "generic/certaintly/orbnorsolya"}}
"""
    try:
        resp = client.chat.completions.create(
            model="sonar",
            messages=[{"role": "user", "content": prompt}],
            response_format={"type": "json_object"}
        )
        return json.loads(resp.choices[0].message.content)
    except Exception as e:
        print(f"  [AI WARN] Analysis failed for {filename}: {e}")
        return {"is_warlock": False, "type": "other"}

# ==========================================
# 6. FILE PATCHERS
# ==========================================
def patch_image(fpath, ai_data):
    try:
        img = Image.open(fpath)
        if ai_data.get("is_warlock") and ai_data.get("type") == "art":
            color = (100, 0, 0, 220)
            artist = BRANDING['warlock_artist_1']
            if ai_data.get("artist") == "orbnorsolya": artist = BRANDING['warlock_artist_2']
            txt = f"© COPYRIGHTED ART | Artist: {artist}"
        else:
            color = (0, 0, 0, 180)
            txt = f"PUBLIC DOMAIN [CC0] | Nexus: {NEXUS_URL}"
        img = img.convert("RGBA")
        w, h = img.size
        draw = ImageDraw.Draw(img)
        draw.rectangle([(0, h-40), (w, h)], fill=color)
        try: font = ImageFont.truetype("arial.ttf", 16)
        except: font = ImageFont.load_default()
        draw.text((20, h-30), f"{txt}", fill=(255,255,255), font=font)
        if fpath.suffix.lower() in ['.jpg', '.jpeg']: img = img.convert("RGB")
        img.save(fpath, quality=95)
    except: pass

def patch_audio(fpath, ai_data, icons):
    try:
        zinger = random.choice(ZINGERS)
        receipt = ASSETS['anthroheartreceipt.png']
        valid = {k:v for k,v in icons.items() if 'receipt' not in k}
        icon_path = random.choice(list(valid.values())) if valid else None
        ext = fpath.suffix.lower()
        if ext == '.mp3':
            try: audio = ID3(fpath)
            except: audio = ID3()
            audio.add(TIT2(encoding=3, text=fpath.stem))
            audio.add(TPE1(encoding=3, text=BRANDING['author']))
            audio.add(TXXX(encoding=3, desc='AnthrOS_Nexus', text=NEXUS_URL))
            audio.add(TXXX(encoding=3, desc='Receipt', text=f"$21k Verified | {receipt}"))
            audio.add(TXXX(encoding=3, desc='Zinger', text=zinger))
            audio.add(COMM(encoding=3, desc='License', text="Public Domain [CC0]"))
            if icon_path:
                with open(icon_path, 'rb') as art:
                    audio.add(APIC(3, 'image/png', 3, 'Cover', art.read()))
            audio.save(fpath)
        elif ext == '.wav':
            audio = WAVE(fpath)
            audio.add_tags()
            audio.tags["ICMT"] = f"AnthrOS Nexus: {NEXUS_URL} | Cost: $21k | License: CC0"
            audio.save(fpath)
    except: pass

def patch_docs(fpath, ai_data):
    try:
        ext = fpath.suffix.lower()
        receipt = ASSETS['anthroheartreceipt.png']
        if ext in ['.txt', '.md']:
            footer = f"\n\n---\nAnthrOS Nexus: {NEXUS_URL}\nVerified Cost: $21k | {receipt}\n"
            with open(fpath, "a", encoding="utf-8") as f: f.write(footer)
        elif ext == '.pdf':
            reader = PdfReader(fpath)
            writer = PdfWriter()
            for p in reader.pages: writer.add_page(p)
            writer.add_metadata({"/Author": BRANDING['author'], "/AnthrOS_Nexus": NEXUS_URL, "/Receipt": f"$21k Verified | {receipt}"})
            with open(fpath, "wb") as f: writer.write(f)
    except: pass

# ==========================================
# 7. HOLLYWOOD GENERATOR
# ==========================================
class HollywoodDoc(FPDF):
    def __init__(self, title, icon_path=None):
        super().__init__()
        self.doc_title = title
        self.icon_path = icon_path
        self.set_auto_page_break(auto=True, margin=20)

    def header(self):
        if self.icon_path:
            try: self.image(self.icon_path, 10, 8, 15)
            except: pass
        self.set_font('Arial', 'B', 10)
        self.cell(0, 10, f"AnthrOS | {self.doc_title}", 0, 0, 'R')
        self.ln(20)

    def cover(self, title, sub):
        self.add_page()
        self.set_fill_color(10, 10, 15)
        self.rect(0,0,210,297,'F')
        if self.icon_path:
            try: self.image(self.icon_path, x=80, y=60, w=50)
            except: pass
        self.set_y(140)
        self.set_text_color(255,255,255)
        self.set_font('Arial','B',24)
        self.multi_cell(0,10, title.upper(), 0, 'C')
        self.ln(10)
        self.set_font('Arial','',12)
        self.set_text_color(0, 240, 255)
        self.multi_cell(0,10, sub, 0, 'C')
        self.add_page()
        self.set_text_color(0,0,0)

    def section(self, title, body):
        self.set_font('Arial','B',14)
        self.set_text_color(0,0,0)
        self.cell(0,10,title,0,1)
        self.set_font('Times','',12)
        self.set_text_color(50,50,50)
        clean = body.encode('latin-1','replace').decode('latin-1')
        self.multi_cell(0,6,clean)
        self.ln(5)

def generate_hollywood(files, icons):
    print(f"\n[ HOLLYWOOD ] Compiling Assets...")
    dest = Path(OUTPUT_DIR) / HOLLYWOOD_DIR
    if not dest.exists(): dest.mkdir(parents=True)

    # Simple defaults if AI fails
    defaults = {"logline": "25 Years of Anthro Legacy.", "hook": "The first public domain Anthro universe."}

    # 1. BIBLE
    try:
        r = client.chat.completions.create(
            model="sonar",
            messages=[{"role":"user","content":"Write TV Bible for Project AnthroHeart. JSON keys: logline, lore, characters."}],
            response_format={"type":"json_object"}
        )
        data = json.loads(r.choices[0].message.content)
    except: 
        data = defaults

    try:
        pdf = HollywoodDoc("Series Bible", icons.get("trinityicon.png"))
        pdf.cover("AnthroHeart Bible", f"Nexus: {NEXUS_URL}")
        pdf.section("Logline", data.get("logline",""))
        pdf.section("Lore", data.get("lore",""))
        pdf.section("Characters", data.get("characters",""))
        pdf.output(dest / "AnthroHeart_Series_Bible.pdf")
    except Exception as e: 
        print(f"  [WARN] Bible skipped: {e}")

    # 2. PITCH DECK
    try:
        r = client.chat.completions.create(
            model="sonar",
            messages=[{"role":"user","content":"Write Pitch Deck for Project AnthroHeart. JSON keys: hook, demographics, viral_loop."}],
            response_format={"type":"json_object"}
        )
        data = json.loads(r.choices[0].message.content)
    except: 
        data = defaults

    try:
        pdf = HollywoodDoc("Pitch Deck", icons.get("blueheartfoxicon.png"))
        pdf.cover("Investment Deck", "The $21k Verified Legacy")
        pdf.section("The Hook", data.get("hook",""))
        pdf.section("Viral Loop", data.get("viral_loop",""))
        pdf.output(dest / "Visual_Pitch_Deck.pdf")
    except: 
        pass

# ==========================================
# 8. MAIN EXECUTION (ROBUST MODE)
# ==========================================
def main():
    print("===================================================")
    print("  ANTHROS INFRASTRUCTURE COMPILER (ROBUST)")
    print("===================================================")

    icons = acquire_assets()
    src = Path(".").resolve() # ABSOLUTE PATH
    dest = (src / OUTPUT_DIR).resolve()
    if not dest.exists(): dest.mkdir()

    files = []
    print("\n[ SCANNING ] Indexing Files...")
    for root, dirs, f_list in os.walk(src):
        if OUTPUT_DIR in root or CACHE_DIR in root: continue
        for f in f_list:
            if f.endswith(".py") or f.endswith(".txt") or f.startswith("."): continue
            files.append(Path(root)/f)

    print(f"  + Found {len(files)} files.")

    print("\n[ COMPILING ] Stamping Nexus Link...")
    for i, fpath in enumerate(files):
        if i % 10 == 0: print(f"\r  Processing... {int(i/len(files)*100)}%", end="")
        try:
            # RELATIVE CALCULATION
            rel_path = fpath.relative_to(src)
            target = dest / rel_path

            # WINDOWS LONG PATH FIX (Magic prefix)
            target_str = str(target.resolve())
            if os.name == 'nt' and len(target_str) > 240:
                target_str = "\\\\?\\" + target_str

            # Create Folder safely
            os.makedirs(os.path.dirname(target_str), exist_ok=True)

            # Copy Safely
            shutil.copy2(fpath, target_str)

            # Patch
            ai_data = analyze_file(fpath.name)
            ext = fpath.suffix.lower()

            # Re-wrap target as Path for patchers
            target_path_obj = Path(target_str)

            if ext in ['.jpg','.png']: patch_image(target_path_obj, ai_data)
            elif ext in ['.mp3','.wav']: patch_audio(target_path_obj, ai_data, icons)
            elif ext in ['.txt','.pdf','.md']: patch_docs(target_path_obj, ai_data)

        except Exception as e:
            # SKIP ERROR AND CONTINUE
            continue

    print("\n  [ DONE ] Metadata Injection Complete.")
    generate_hollywood(files, icons)

    print("\n===================================================")
    print("  INFRASTRUCTURE COMPILED.")
    print("===================================================")

if __name__ == "__main__":
    main()
